package com.hu.bgp.client;

import com.google.gwt.core.client.GWT;
import com.google.gwt.dom.client.Element;
import com.google.gwt.user.client.DOM;
import com.google.gwt.user.client.Timer;
import com.google.gwt.user.client.Window;
import com.google.gwt.user.client.rpc.AsyncCallback;
import com.google.gwt.user.client.rpc.ServiceDefTarget;
import com.google.gwt.user.client.ui.RootPanel;
import com.hu.bgp.client.eventservice.BgpRemoteEventServiceFactory;
import com.hu.bgp.client.rpc.BgpService;
import com.hu.bgp.client.rpc.BgpServiceAsync;
import com.hu.bgp.framework.clientapi.BoardGameService;
import com.hu.bgp.framework.clientapi.FailureHandler;
import com.hu.bgp.framework.clientapi.FailureHandlingCallback;
import com.hu.bgp.framework.clientapi.util.Firebug;
import com.hu.bgp.shared.BoardGameMessage;
import com.hu.bgp.shared.Message;

import com.hu.bgp.shared.data.ClientGameType;

import de.novanic.eventservice.client.event.Event;
import de.novanic.eventservice.client.event.RemoteEventService;
import de.novanic.eventservice.client.event.listener.RemoteEventListener;

public class GameLoader implements FailureHandler
{
	private BgpServiceAsync bgpService;
	private ClientGameType gameType;

	public GameLoader() {
		bgpService = GWT.create(BgpService.class);
		ServiceDefTarget target = (ServiceDefTarget) bgpService;
		target.setServiceEntryPoint("/bgp/bgpService");
		exportInitNameSpace();
	}

	// TODO Implement correctly, right now for testing this method just creates
	// and join a tictactie instance
	public void loadGame(ClientGameType gameType) {

	this.gameType = gameType;
//		bgpService.createGame(gameType.getAlias(), new AsyncCallback<Void>() {
//
//			public void onFailure(Throwable caught) {
//				// TODO Auto-generated method stub
//
//			}
//
//			public void onSuccess(Void result) {
//				// TODO Auto-generated method stub
//
//			}
//
//		});
		
		Firebug.debug("loadGame("+gameType.getAlias()+")");
		try{
		loadGame(gameType.getAlias());
		}catch (Exception e) {
			Firebug.debug(e.getMessage());
		}
		Firebug.debug("timer start");
		Timer timerTest = new Timer() {

			@Override
			public void run() {
				// TODO Auto-generated method stub

				if (isLoaded()) {
					createListner();
					cancel();
				}
			}

		};
		timerTest.scheduleRepeating(100);
		timerTest.run();
	}

	// TODO remove old stuf but maybe intergrated the delegated failure... its
	// nice!
	// bgpService.getClientGameContext(new
	// FailureHandlingCallback<ClientGameContext>(this)
	// {
	// public void onSuccess(ClientGameContext result)
	// {
	// clientGameContext = result;
	//
	// // listeners for incoming game-wide events
	// RemoteEventService theRemoteEventService =
	// BgpRemoteEventServiceFactory.getInstance().getRemoteEventService();
	// theRemoteEventService.addListener(clientGameContext.getGameDomain(), new
	// GameDomainEventListener());
	// \
	//
	// }
	// });
	// }
	
	//doesn't work any more
	private void createListner() {
//		bgpService.getClientGameContext(gameType.,gameType.getAlias()new AsyncCallback<ClientGameContext>() {
//
//			public void onFailure(Throwable caught) {
//				// TODO Handle failure properly, through Failure handle? or
//				// implenmentationm right here
//				Window.alert("Failure to get GAME CONTEXT!");
//			}
//
//			public void onSuccess(ClientGameContext result) {
//				// TODO Auto-generated method stub
//				RemoteEventService theRemoteEventService = BgpRemoteEventServiceFactory
//						.getInstance().getRemoteEventService();
//				theRemoteEventService.addListener(result.getGameDomain(),
//						new GameDomainEventListener());
//			}
//
//		});
	}

	private class GameDomainEventListener implements RemoteEventListener
	{
		public void apply(Event event) {

			if (event instanceof BoardGameMessage) {

				BoardGameMessage messageEvent = (BoardGameMessage) event;
				pushEvent(messageEvent.getPayload());
			}
		}
	}

	private void loadGame(String gameAlias) {
		// GWT.log("test: " + gameTypeTable.getSelection().getDisplayName());
		RootPanel content = RootPanel.get("content");
		content.getElement().setInnerHTML("");
		// GWT.log("content panel cleared");

		Element body = RootPanel.getBodyElement();
		Element head = body.getParentElement().getFirstChildElement();
		// GWT.log(head.getInnerHTML());

		Element script = DOM.createElement("script");
		script.setAttribute("type", "text/javascript");
		script.setAttribute("language", "javascript");
		script.setAttribute("src", "/resources/" + gameAlias + "/" + gameAlias
				+ ".nocache.js");
		head.appendChild(script);
		GWT.log(head.getInnerHTML());
	}

	public native void exportInitNameSpace() /*-{
		if(!$wnd['bgpenv']){
			$wnd['bgpenv'] = []};
			$wnd['bgpenv'].isLoaded = false;
	}-*/;

	public native boolean isLoaded() /*-{
		console.debug("isLoaded:"+$wnd['bgpenv'].isLoaded);
		return $wnd['bgpenv'].isLoaded;
	}-*/;

	public native void pushEvent(String payload) /*-{
		console.debug("pushEvent: "+payload);
		return $wnd['bgpenv'].sendRawGWTObject(payload);
	}-*/;

	public void onFailure(Throwable caught) {
		// TODO Auto-generated method stub

	}
}
